﻿/********************************************************
 * Module Name    : Workflow
 * Purpose        : 
 * Class Used     : X_AD_WF_NextCondition
 * Chronological Development
 * Veena Pandey     02-May-2009
 ******************************************************/

using System;
using System.Collections.Generic;
//using System.Linq;
using System.Text;
using VAdvantage.Classes;
using VAdvantage.Model;
//using System.Numeric;
using VAdvantage.Utility;

namespace VAdvantage.WF
{
    public class MWFNextCondition : X_AD_WF_NextCondition
    {
        /**	Numeric evaluation		*/
        private bool _numeric = true;

        /// <summary>
        /// Default Constructor
        /// </summary>
        /// <param name="ctx">context</param>
        /// <param name="id">id</param>
        /// <param name="trxName">transaction</param>
        public MWFNextCondition(Ctx ctx, int id, String trxName)
            : base(ctx, id, trxName)
        {
            
        }

        

        /// <summary>
        /// Load Cosntructor
        /// </summary>
        /// <param name="ctx">context</param>
        /// <param name="rs">result set</param>
        /// <param name="trxName">transaction</param>
        public MWFNextCondition(Ctx ctx, System.Data.DataRow rs, String trxName)
            : base(ctx, rs, trxName)
        {
        }

        /// <summary>
        /// Is Or Condition
        /// </summary>
        /// <returns>true if OR</returns>
        public bool IsOr()
        {
            return ANDOR_Or.Equals(GetAndOr());
        }

        /// <summary>
        /// Evaluate Condition
        /// </summary>
        /// <param name="activity">activity</param>
        /// <returns>true if true</returns>
        public bool Evaluate(MWFActivity activity)
	    {
            if (GetAD_Column_ID() == 0)
            {
                //throw new IllegalStateException("No Column defined - " + this);
                throw new Exception("No Column defined - " + this);
            }
    		
            

            PO po = activity.GetPO();
            if (po == null || po.Get_ID() == 0)
            {
                //throw new IllegalStateException("Could not evaluate " + po + " - " + this);
                throw new Exception("Could not evaluate " + po + " - " + this);
            }
            //
            Object valueObj = po.Get_ValueOfColumn(GetAD_Column_ID());
            if (valueObj == null)
                valueObj = "";
            String value1 = GetValue();
            if (value1 == null)
                value1 = "";
            String value2 = GetValue2();
            if (value2 == null)
                value2 = "";
    		
            String resultStr = "PO:{" + valueObj + "} " + GetOperation() + " Condition:{" + value1 + "}";
            if (GetOperation().Equals(OPERATION_Sql))
                throw new ArgumentException("SQL Operator not implemented yet: " + resultStr);
            if (GetOperation().Equals(OPERATION_X))
                resultStr += "{" + value2 + "}";
            
            bool result = false;
            //if (valueObj instanceof Number)
            if (valueObj != null && CommonFunctions.IsNumeric(valueObj.ToString()))
                result = CompareNumber(valueObj, value1, value2);
            else
                result = CompareString(valueObj, value1, value2);
            //
            log.Fine(resultStr + " -> " + result + (_numeric ? " (#)" : " ($)"));
            return result;
	    }

        /// <summary>
        /// Compare String
        /// </summary>
        /// <param name="valueObj">comparator</param>
        /// <param name="value1S">first value</param>
        /// <param name="value2S">second value</param>
        /// <returns>true if operation</returns>
        private bool CompareString(Object valueObj, String value1S, String value2S)
        {
            _numeric = false;
            String valueObjS = valueObj.ToString();
            //
            String op = GetOperation();
            if (OPERATION_Eq.Equals(op))
                return valueObjS.CompareTo(value1S) == 0;
            else if (OPERATION_Gt.Equals(op))
                return valueObjS.CompareTo(value1S) > 0;
            else if (OPERATION_GtEq.Equals(op))
                return valueObjS.CompareTo(value1S) >= 0;
            else if (OPERATION_Le.Equals(op))
                return valueObjS.CompareTo(value1S) < 0;
            else if (OPERATION_LeEq.Equals(op))
                return valueObjS.CompareTo(value1S) <= 0;
            else if (OPERATION_Like.Equals(op))
                return valueObjS.CompareTo(value1S) == 0;
            else if (OPERATION_NotEq.Equals(op))
                return valueObjS.CompareTo(value1S) != 0;
            //
            else if (OPERATION_Sql.Equals(op))
                throw new ArgumentException("SQL not Implemented");
            //
            else if (OPERATION_X.Equals(op))
            {
                if (valueObjS.CompareTo(value1S) < 0)
                    return false;
                //	To
                return valueObjS.CompareTo(value2S) <= 0;
            }
            //
            throw new ArgumentException("Unknown Operation=" + op);
        }

        /// <summary>
        /// Compare Number
        /// </summary>
        /// <param name="valueObj">comparator</param>
        /// <param name="value1">first value</param>
        /// <param name="value2">second value</param>
        /// <returns>true if operation</returns>
        private bool CompareNumber (Object valueObj, String value1, String value2)
	    {
		    Decimal valueObjB = 0;
		    Decimal value1B = 0;
		    Decimal value2B = 0;
		    try
		    {
                
                //if (valueObj instanceof BigDecimal)
                //    valueObjB = (BigDecimal)valueObj;
                //else if (valueObj instanceof Integer)
                //    valueObjB = new BigDecimal (((Integer)valueObj).intValue());
                //else
                //    valueObjB = new BigDecimal (String.valueOf(valueObj));

                valueObjB = Convert.ToDecimal(valueObj);
		    }
		    catch (Exception e)
		    {
			    log.Fine("compareNumber - valueObj=" + valueObj + " - " + e.ToString());
			    return CompareString(valueObj, value1, value2);
		    }
		    try
		    {
                value1B = Convert.ToDecimal(value1);
		    }
		    catch (Exception e)
		    {
			    log.Fine("compareNumber - value1=" + value1 + " - " + e.ToString());
			    return CompareString(valueObj, value1, value2);
		    }
    		
		    String op = GetOperation();
		    if (OPERATION_Eq.Equals(op))
			    return valueObjB.CompareTo(value1B) == 0;
		    else if (OPERATION_Gt.Equals(op))
			    return valueObjB.CompareTo(value1B) > 0;
		    else if (OPERATION_GtEq.Equals(op))
			    return valueObjB.CompareTo(value1B) >= 0;
		    else if (OPERATION_Le.Equals(op))
			    return valueObjB.CompareTo(value1B) < 0;
		    else if (OPERATION_LeEq.Equals(op))
			    return valueObjB.CompareTo(value1B) <= 0;
		    else if (OPERATION_Like.Equals(op))
			    return valueObjB.CompareTo(value1B) == 0;
		    else if (OPERATION_NotEq.Equals(op))
			    return valueObjB.CompareTo(value1B) != 0;
		    //
		    else if (OPERATION_Sql.Equals(op))
			    throw new ArgumentException("SQL not Implemented");
		    //
		    else if (OPERATION_X.Equals(op))
		    {
			    if (valueObjB.CompareTo(value1B) < 0)
				    return false;
			    //	To
			    try
			    {
                    value2B = Convert.ToDecimal(value2);
				    return valueObjB.CompareTo(value2B) <= 0;
			    }
			    catch (Exception e)
			    {
				    log.Fine("compareNumber - value2=" + value2 + " - " + e.ToString());
				    return false;
			    }
		    }
		    //
		    throw new ArgumentException("Unknown Operation=" + op);
	    }
    }
}
